import { forwardRef, useImperativeHandle, useRef, useState } from 'react';

import { Alert, Radio } from 'antd';

import Text from '@/components/text';

import { SearchType } from '@/enum';
import {
  ActionType,
  ProTable as AntProTable,
  ProTableProps as AntProTableProps,
  ParamsType,
  RequestData
} from '@ant-design/pro-components';

export type ProTableProps<T, U, ValueType = 'text'> = AntProTableProps<T, U, ValueType> & {
  /** 是否开启精确模糊筛选切换功能, 默认开启 */
  searchType?: boolean;
};

export type ProTableRef<T, U, ValueType = 'text'> = {};

const ProTable = <
  T extends Record<string, any>,
  U extends ParamsType = ParamsType,
  ValueType = 'text'
>(
  {
    searchType: searchTypeProp = true,
    request: requestProp,
    tableExtraRender: tableExtraRenderProp,
    actionRef: actionRefProp,
    ...rest
  }: ProTableProps<T, U, ValueType>,
  ref: React.Ref<ProTableRef<T, U, ValueType>>
) => {
  type P = ProTableProps<T, U, ValueType>;
  const actionRef = useRef<ActionType>();
  const [error, setError] = useState<Error>();
  // 查询类型 模糊或者精确
  const [searchType, setSearchType] = useState<SearchType>(SearchType.模糊);

  // 传递actionRef
  useImperativeHandle(actionRefProp, () => {
    return actionRef.current;
  });
  useImperativeHandle(ref, () => {
    return {};
  });
  const request: P['request'] = requestProp
    ? (query, ...args) => {
        setError(undefined);

        const _query = {
          ...query
        } as Record<string, any>;

        if (searchTypeProp) {
          _query.likeFlag = searchType;
        }

        return requestProp(_query as U, ...args).catch((e) => {
          setError(e as Error);
        }) as Promise<Partial<RequestData<T>>>;
      }
    : requestProp;

  const tableExtraRender: P['tableExtraRender'] = (...args) => {
    return (
      <>
        {tableExtraRenderProp?.(...args)}
        {error && (
          <Alert
            message={
              <div>
                {error.message}{' '}
                <Text
                  onClick={() => {
                    actionRef.current?.reload();
                  }}
                >
                  重试
                </Text>
              </div>
            }
            type="error"
            showIcon
          />
        )}
      </>
    );
  };

  const search: P['search'] =
    searchTypeProp === true
      ? {
          optionRender: (searchConfig, formProps, dom) => [
            <Radio.Group
              key="type"
              value={searchType}
              onChange={(e) => {
                setSearchType(e.target.value);
              }}
              size="small"
            >
              <div>
                <Radio value={SearchType.模糊}>模糊查询</Radio>
              </div>
              <div>
                <Radio value={SearchType.精确}>精确查询</Radio>
              </div>
            </Radio.Group>,
            ...dom.reverse()
          ]
        }
      : undefined;

  return (
    <AntProTable<T, U, ValueType>
      request={request}
      tableExtraRender={tableExtraRender}
      actionRef={actionRef}
      search={search}
      rowKey="id"
      scroll={{
        x: 'max-content'
      }}
      pagination={{
        defaultPageSize: 10
      }}
      {...rest}
    />
  );
};

export default forwardRef(ProTable) as <
  T,
  U = {},
  // 自动注入全局的ValueType
  _ValueType = 'text',
  ValueType = _ValueType | GlobalValueType
>(
  props: ProTableProps<T, U, ValueType> & {
    ref?: React.Ref<ProTableRef<T, U, ValueType>>;
  }
) => React.ReactElement;
